package com.bj58.data.emailreports.utils;

import java.lang.reflect.Field;
import java.util.ArrayList;
import java.util.Comparator;
import java.util.Date;
import java.util.Iterator;
import java.util.List;
import java.util.ListIterator;
import java.util.TreeSet;


/**
 * @author huangliang
 *升序  将List<String>  String(key_count)  根据count大小排序
 */
@SuppressWarnings("rawtypes")
class SortComparator implements Comparator {


	public int compare(Object o1, Object o2) {
	
	 if (o1 == null || o2 == null)
        
           return 0; 
		
     int v1 = Integer.parseInt(o1.toString().substring(o1.toString().indexOf("_")+1));
	
	 int v2 = Integer.parseInt(o2.toString().substring(o2.toString().indexOf("_")+1));
      
         return v1>v2?1:-1;
	
    }

}


/**
 * @author huangliang
 *升序  将List<String>  String(key_count)  根据key(int)大小排序
 */
@SuppressWarnings("rawtypes")
class SortComparator_key_int implements Comparator {


	public int compare(Object o1, Object o2) {
	
	 if (o1 == null || o2 == null)
        
           return 0; 
		
     int v1 = Integer.parseInt(o1.toString().substring(0,o1.toString().indexOf("_")));
	
	 int v2 = Integer.parseInt(o2.toString().substring(0,o2.toString().indexOf("_")));
      
         return v1>v2?1:-1;
	
    }

}


/**
 * @author huangliang
 *升序  将List<String>  String(key_count)  根据key(date)大小排序
 */
@SuppressWarnings("rawtypes")
class SortComparator_key_date implements Comparator {


	public int compare(Object o1, Object o2) {
	
		 if (o1 == null || o2 == null)
	        
	           return 0; 
			
	     Date v1 = DateUtil.parseSimpleDateTime((o1.toString().substring(0,o1.toString().indexOf("_"))), "yyyy-MM-dd");
		
	     Date v2 = DateUtil.parseSimpleDateTime((o2.toString().substring(0,o2.toString().indexOf("_"))), "yyyy-MM-dd");
	     
	     
	      
	     return v1.after(v2)?1:-1;
		
    }

}




/**
 * @author huangliang
 *降序
 */
@SuppressWarnings("rawtypes")
class DescendComparator implements Comparator { 

	public int compare(Object o1, Object o2) {
	
	 if (o1 == null || o2 == null)
        
           return 0; 
		
     double v1 = Double.valueOf(o1.toString().substring(o1.toString().indexOf("_")+1));
	
     double v2 = Double.valueOf(o2.toString().substring(o2.toString().indexOf("_")+1));
      
         return v1<v2?1:-1;
	
    }

}


public class SortUtil {
	private ReflectUtil reflectUtil = new ReflectUtil();
	
	/**对key_count集合进行排序获取count后10的集合
	 * @param values
	 * @return
	 */
	@SuppressWarnings("unchecked")
	public static List<String> AscTOP10(List<String> values){
		//排序
		SortComparator cc=new SortComparator();
		TreeSet<String> ts=new TreeSet<String>(cc);
		ts.addAll(values);
		//截取前10个
		List<String> sortValues = new ArrayList<String>();
		int count = 0;
		Iterator<String> it = ts.iterator();
		while(it.hasNext()){
			sortValues.add(it.next());
			count++;
			if(count == 10){
				break;
			}
		}
		
		return sortValues;
	}
	
	/**对key_count集合进行排序获取count前10的集合
	 * @param values
	 * @return
	 */
	@SuppressWarnings("unchecked")
	public static List<String> DescendTOP10(List<String> values){
		//排序
		DescendComparator cc=new DescendComparator();
		TreeSet<String> ts=new TreeSet<String>(cc);
		ts.addAll(values);
		//截取前10个
		List<String> sortValues = new ArrayList<String>();
		int count = 0;
		Iterator<String> it = ts.iterator();
		while(it.hasNext()){
			sortValues.add(it.next());
			count++;
			if(count == 10){
				break;
			}
		}
		
		return sortValues;
	}
	
	
	
	/**对key_count集合进行降序排序(按照count数值大小)  并取前max个
	 * @param values
	 * @param max  排序后取前多少个
	 * @return
	 */
	@SuppressWarnings("unchecked")
	public static List<String> DescendByCount(List<String> values,int max){
		//排序
		DescendComparator cc=new DescendComparator();
		TreeSet<String> ts=new TreeSet<String>(cc);
		ts.addAll(values);
		//截取前max个
		List<String> sortValues = new ArrayList<String>();
		int count = 0;
		Iterator<String> it = ts.iterator();
		while(it.hasNext()){
			sortValues.add(it.next());
			count++;
			if(count == max){
				break;
			}
		}
		
		return sortValues;
	}
	
	
	/**对key_count集合进行升序排列  （按照KEY(int)）大小
	 * @param values
	 * @return
	 */
	@SuppressWarnings("unchecked")
	public static List<String> AscByKey_int(List<String> values){
		SortComparator_key_int cc=new SortComparator_key_int();
		TreeSet<String> ts=new TreeSet<String>(cc);
		ts.addAll(values);
		return new ArrayList<String>(ts);
	}
	
	/**对key_count集合进行升序排列  （按照KEY(date)）大小
	 * @param values
	 * @return
	 */
	@SuppressWarnings("unchecked")
	public static List<String> AscByKey_date(List<String> values){
		SortComparator_key_date cc=new SortComparator_key_date();
		TreeSet<String> ts=new TreeSet<String>(cc);
		ts.addAll(values);
		return new ArrayList<String>(ts);
	}
	
	/** 自定义报表  跨表查询 重新排序
	 * @param dataList
	 * @param orderBy
	 * @param cols
	 * @return
	 */
	public static List<String>  sortIRData(List<String> dataList , String orderBy,List<String> cols){
		//确认排序指标位置及排序方式
		List<String>  sortValues = new ArrayList<String>();//下标_排序方式_
		String[] orderByArray = orderBy.replace("order by", "").trim().split(",");
		for(int i = 0 ; i < cols.size() ; i++){
			String col = cols.get(i);
			if(orderBy.contains(col)){
				for(String order : orderByArray){
					if(order.contains(col)){
						String orderType = order.replace(col, "").trim();
						if("".equals(orderType)){
							orderType = "asc";
						}
						sortValues.add(i+"_"+orderType);
					}
				}
			}
		}
		//根据排序值及排序方式的不同 进行多次分组排序
		String[] sampleDateArray = dataList.get(0).split(";"); //数据样本
		for(String sortValue : sortValues){
			int index = Integer.parseInt(sortValue.split("_")[0]);//下标
			String orderType = sortValue.split("_")[1];//排序方式
			//从数据样本取出排序值  判断类型
			String orderSample = sampleDateArray[index];
			
			if(PatternUtil.hasContainsChinese(orderSample)){//中文
				
			}else if(PatternUtil.isDate(orderSample)){//日期
				
			}else{ //数值
				
			}
			
		}
		
		return dataList;
	}
	
	
	
	@SuppressWarnings("unchecked")
    //对上述快排函数原型修改，使其可以对任意对象类型数组进行排序。这个函数为内部使用，外部排序函数接口为sort()，
    //sort函数要求对象必须实现Comparable接口，可以提供编译时类型检测，见后文。
    private static void quickSort(Object[] in,int begin, int end) {
        if( begin == end || begin == (end-1) ) return;
        Object p = in[begin];
        int a = begin +1;
        int b = a;
        for( ; b < end; b++) {
            //该对象类型数组必须实现Comparable接口，这样才能使用compareTo函数进行比较
            if( ((Comparable<Object>)in[b]).compareTo(p) < 0) {
                if(a == b){a++; continue;}
                Object temp = in[a];
                in[a] = in[b];
                in[b] = temp;
                a++;
            }
        }
        in[begin] = in[a-1];
        in[a-1] = p;
        if( a-1 > begin){
            quickSort(in,begin, a);
        } 
        if( end-1 > a ) {
            quickSort(in,a, end);
        } 
        return;
    }
    
    //使用泛型，对任意对象数组排序，该对象类型数组必须实现Comparable接口
    public static <T extends Comparable<? super T>> void sort(T[] input){
        quickSort(input,0,input.length);
    }
    
    //添加对List对象进行排序的功能，参考了Java中的Java.util.Collections类的sort()函数
    public static <T extends Comparable<? super T>> void sort(List<T> list){
        Object[] t = list.toArray();//将列表转换为数组
        quickSort(t,0,t.length); //对数组进行排序
        //数组排序完成后再写回到列表中
        ListIterator<T> i = list.listIterator();
        for (int j=0; j<t.length; j++) {
            i.next();
            i.set((T)t[j]);
        }
    }
    
    //由于Java中原始数据类型（int、double、byte等）无法使用泛型，所以只能使用函数重载机制实现对这些原始类型数组（int[]、double[]、byte[]等）的排序。
    //这里为了共用同一个排序函数，利用原始类型的(AutoBoxing，UnBoxing)机制将其封装为对应对象类型，组成新的对象数组，排序后再解封装，
    //这样的缺点是需要额外的转换步骤、额外的空间保存封装后的数组。另一种方式是将排序代码复制到各个重载函数中，
    //官方API中的Java.util.Arrays这个类中的sort()函数就是使用这种方法，可以从Arrays类的源代码看出。
    public static void sort(int[] input){
        Integer[] t = new Integer[input.length];
        for(int i = 0; i < input.length; i++){
            t[i] = input[i];//封装
        }
        quickSort(t,0,t.length);//排序
        for(int i = 0; i < input.length; i++){
            input[i] = t[i];//解封装
        }
    }
    //double[]数组的重载函数
    public static void sort(double[] input){
        Double[] t = new Double[input.length];
        for(int i = 0; i < input.length; i++){
            t[i] = input[i];
        }
        quickSort(t,0,t.length);
        for(int i = 0; i < input.length; i++){
            input[i] = t[i];
        }
    }
    //byte[]数组的重载函数
    public static void sort(byte[] input){
        Byte[] t = new Byte[input.length];
        for(int i = 0; i < input.length; i++){
            t[i] = input[i];
        }
        quickSort(t,0,t.length);
        for(int i = 0; i < input.length; i++){
            input[i] = t[i];
        }
    }
    //short[]数组的重载函数
    public static void sort(short[] input){
        Short[] t = new Short[input.length];
        for(int i = 0; i < input.length; i++){
            t[i] = input[i];
        }
        quickSort(t,0,t.length);
        for(int i = 0; i < input.length; i++){
            input[i] = t[i];
        }
    }
    //char[]数组的重载函数
    public static void sort(char[] input){
        Character[] t = new Character[input.length];
        for(int i = 0; i < input.length; i++){
            t[i] = input[i];
        }
        quickSort(t,0,t.length);
        for(int i = 0; i < input.length; i++){
            input[i] = t[i];
        }
    }
    //float[]数组的重载函数
    public static void sort(float[] input){
        Float[] t = new Float[input.length];
        for(int i = 0; i < input.length; i++){
            t[i] = input[i];
        }
        quickSort(t,0,t.length);
        for(int i = 0; i < input.length; i++){
            input[i] = t[i];
        }
    }
    
    
    
    /**根据指定字段大小对List<T>进行排序    指定字段必须为数字(int or double)
     * @param <T>
     * @param rsList
     * @param clazz
     * @param fileName
     * @param sortType   1:升序  2:降序
     * @return
     * @throws Exception
     */
    @SuppressWarnings({ "static-access"})
	public <T>List<T>  sortListByFileNameVo(List<T> rsList , Class<T> clazz , String fileName, int sortType)throws Exception{
    	
		//字段数据类型
		Field field = clazz.getDeclaredField(fileName);
		Class<?> filedCls = field.getType();
		
		for(int i = 0 ; i < rsList.size() - 1 ; i ++){
			T tempVo1 = clazz.newInstance();
			T tempVo2 = clazz.newInstance();
			for(int j = 0 ; j <  rsList.size() - 1 - i ; j++){
				Object value1 = reflectUtil.getGetterMethod(clazz, clazz.getDeclaredField(fileName)).invoke(rsList.get(j));
				Object value2 = reflectUtil.getGetterMethod(clazz, clazz.getDeclaredField(fileName)).invoke( rsList.get(j+1));
				
				
				if(filedCls == int.class || filedCls == Integer.class || filedCls == long.class || filedCls == Long.class) {
					int comp1 = Integer.parseInt(value1.toString());
					int comp2 = Integer.parseInt(value2.toString());
					if(sortType == 1){ //升序
						if(comp1 > comp2){
							tempVo1 = rsList.get(j);
							tempVo2 = rsList.get(j+1);
							
							rsList.remove(j+1);
							rsList.remove(j);
							
							rsList.add(j, tempVo2);
							rsList.add(j+1, tempVo1);
							
						}
					}else if(sortType == 2){ //降序
						if(comp1 < comp2){
							tempVo1 = rsList.get(j);
							tempVo2 = rsList.get(j+1);
							
							rsList.remove(j+1);
							rsList.remove(j);
							
							rsList.add(j, tempVo2);
							rsList.add(j+1, tempVo1);
							
						}
					}
					
				}else if(filedCls == double.class || filedCls == Double.class) {
					double comp1 = Double.parseDouble(value1.toString());
					double comp2 = Double.parseDouble(value2.toString());
					if(sortType == 1){ //升序
						if(comp1 > comp2){
							tempVo1 = rsList.get(j);
							tempVo2 = rsList.get(j+1);
							
							rsList.remove(j+1);
							rsList.remove(j);
							
							rsList.add(j, tempVo2);
							rsList.add(j+1, tempVo1);
							
						}
					}else if(sortType == 2){ //降序
						if(comp1 < comp2){
							tempVo1 = rsList.get(j);
							tempVo2 = rsList.get(j+1);
							
							rsList.remove(j+1);
							rsList.remove(j);
							
							rsList.add(j, tempVo2);
							rsList.add(j+1, tempVo1);
							
						}
					}
				} 
				
			}
			
		}
		
		
    	return rsList;
    }
    
    
 
    
    /**根据指定字符串下标位置对List<String>进行排序    指定字段必须为数字(int or double)
     * @param <T>
     * @param rsList
     * @param sortValueIndex  排序字段下标位置
     * @param sortType   1:升序  2:降序
     * @return
     * @throws Exception
     */
	public static List<String>  sortListByFileName(List<String> rsList ,int sortValueIndex, int sortType)throws Exception{
    	
		for(int i = 0 ; i < rsList.size() - 1 ; i ++){
			String tempVo1 = "";
			String tempVo2 = "";
			for(int j = 0 ; j <  rsList.size() - 1 - i ; j++){
				
				Object value1 = rsList.get(j).split(";")[sortValueIndex];
				Object value2 = rsList.get(j+1).split(";")[sortValueIndex];
				
				
				if(!value1.toString().contains(".")) { //整型
					
					int comp1 =0;
					int comp2 =0;	
					if(!value1.equals("--")){
						comp1 = Integer.parseInt(value1.toString().replaceAll(",", ""));
					}
					if(!value2.equals("--")){
						comp2 = Integer.parseInt(value2.toString().replaceAll(",", ""));
					}
					
					if(sortType == 1){ //升序
						if(comp1 > comp2){
							tempVo1 = rsList.get(j);
							tempVo2 = rsList.get(j+1);
							
							rsList.remove(j+1);
							rsList.remove(j);
							
							rsList.add(j, tempVo2);
							rsList.add(j+1, tempVo1);
							
						}
					}else if(sortType == 2){ //降序
						if(comp1 < comp2){
							tempVo1 = rsList.get(j);
							tempVo2 = rsList.get(j+1);
							
							rsList.remove(j+1);
							rsList.remove(j);
							
							rsList.add(j, tempVo2);
							rsList.add(j+1, tempVo1);
							
						}
					}
					
				}else{
					double comp1 = Double.parseDouble(value1.toString());
					double comp2 = Double.parseDouble(value2.toString());
					if(sortType == 1){ //升序
						if(comp1 > comp2){
							tempVo1 = rsList.get(j);
							tempVo2 = rsList.get(j+1);
							
							rsList.remove(j+1);
							rsList.remove(j);
							
							rsList.add(j, tempVo2);
							rsList.add(j+1, tempVo1);
							
						}
					}else if(sortType == 2){ //降序
						if(comp1 < comp2){
							tempVo1 = rsList.get(j);
							tempVo2 = rsList.get(j+1);
							
							rsList.remove(j+1);
							rsList.remove(j);
							
							rsList.add(j, tempVo2);
							rsList.add(j+1, tempVo1);
							
						}
					}
				} 
				
			}
		}
		
    	return rsList;
    }
    
}

